﻿using System;
using System.Linq;
using System.IO;
using System.Text;
using System.Collections.Generic;
using System.Windows.Forms;
using System.Drawing;
using System.Net;
using System.Xml.Linq;
using SourceAFIS.Simple;

namespace FingerprintTest
{
    public partial class frmMain : Form
    {
        private string imagePath = Path.GetFullPath("images");  //图片路径
        private AfisEngine afis = new AfisEngine();              //指纹引擎

        public frmMain()
        {
            InitializeComponent();
        }

        private void frmMain_Load(object sender, EventArgs e)
        {
            cbTemplateType.SelectedIndex = 0;
        }

        
        [Serializable]
        class MyFingerprint : Fingerprint
        {
            public string Filename;
        }

        [Serializable]
        class MyPerson : Person
        {
            public string Name;
        }

        private void btnVerify_Click(object sender, EventArgs e)
        {

            //加载人员指纹列表
            List<MyPerson> personList = new List<MyPerson>();
            personList.Add(Enroll(Path.Combine(imagePath, "A.tif"), "A"));
            personList.Add(Enroll(Path.Combine(imagePath, "B.tif"), "B"));
            personList.Add(Enroll(Path.Combine(imagePath, "C.tif"), "C"));

            //待验证人员指纹
            MyPerson person = Enroll(Path.Combine(imagePath, "X.tif"), "X");

            txtContent.Clear();
            foreach (MyPerson p in personList)
            {
                float score = afis.Verify(person, p);
                txtContent.AppendText(person.Name + " score " + score + "\r\n");
            }

            afis.Threshold = 10;  //设置识别阀值
            MyPerson match = afis.Identify(person, personList).FirstOrDefault() as MyPerson;

        }

        /// <summary>
        /// 提取指纹模板
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void btnExtractTemplate_Click(object sender, EventArgs e)
        {
            //指纹图片列表
            List<String> imageList = new List<String>();
            imageList.Add(Path.Combine(imagePath, "A.tif"));
            imageList.Add(Path.Combine(imagePath, "B.tif"));
            imageList.Add(Path.Combine(imagePath, "C.tif"));
            imageList.Add(Path.Combine(imagePath, "tang1.jpg"));
            imageList.Add(Path.Combine(imagePath, "tang2.jpg"));
            imageList.Add(Path.Combine(imagePath, "lihe.jpg"));

            //提取指纹
            txtContent.Clear();
            foreach (String imageUrl in imageList)
            {
                Fingerprint fp = ExtractFingerprint(imageUrl);
                string content = Path.GetFileName(imageUrl) + " iso template:\r\n" + Convert.ToBase64String(fp.AsIsoTemplate);
                txtContent.AppendText(content + "\r\n\r\n");

                //Console.WriteLine(Path.GetFileName(imageUrl)+" xml template" + fp.AsXmlTemplate.ToString());
            }

        }

        private void btnSelectImage_Click(object sender, EventArgs e)
        {
            DialogResult result = ofdSelectImage.ShowDialog();
            if (result != DialogResult.OK)
            {
                return;
            }

            string fileName = ofdSelectImage.FileName;
            string server = tbServer.Text.Trim();
            string type = cbTemplateType.SelectedItem.ToString();
            string responseStr = ExtractTemplate("http://" + server + "/FpHandler.ashx?method=extract&type=" + type, fileName);

            txtContent.Text = responseStr;
        }

        /// <summary>
        /// 提取指纹模板
        /// </summary>
        /// <param name="address">请求地址</param>
        /// <param name="filename">图片文件路径</param>
        /// <returns>返回json</returns>
        public string ExtractTemplate(string address, string filename)
        {
            string resultStr = "";

            //检查文件是否存在  
            if (!File.Exists(filename))
            {
                MessageBox.Show("{0} does not exist!", filename);
                return resultStr;
            }


            try
            {
                WebClient webClient = new WebClient();
                byte[] bytes = webClient.UploadFile(address, "POST", filename);

                resultStr = Encoding.GetEncoding("utf-8").GetString(bytes);
            }
            catch (Exception e)
            {
                MessageBox.Show(e.StackTrace);
            }

            return resultStr;
        }

        /// <summary>
        /// 注册人员
        /// </summary>
        /// <param name="filename">指纹图片路径</param>
        /// <param name="name">人员名称</param>
        /// <returns>人员</returns>
        private MyPerson Enroll(string filename, string name)
        {
            //创建指纹对象
            MyFingerprint fp = new MyFingerprint();
            using (Bitmap bitmap = new Bitmap(filename))
            {
                fp.Filename = filename;
                fp.AsBitmap = bitmap;
            }

            Console.WriteLine(" Image size = {0} x {1} (width x height)", fp.Image.GetLength(1), fp.Image.GetLength(0));

            //创建人对象
            MyPerson person = new MyPerson();
            person.Name = name;
            person.Fingerprints.Add(fp);    //加入指纹

            //提取指纹摸版
            afis.Extract(person);
            Console.WriteLine(" Template size = {0} bytes", fp.Template.Length);

            return person;
        }

        /// <summary>
        /// 创建图片指纹对象
        /// </summary>
        /// <param name="filename">图片绝对路径</param>
        /// <returns>指纹对象</returns>
        private Fingerprint ExtractFingerprint(string filename)
        {
            //创建指纹对象
            Fingerprint fp = new Fingerprint();
            using (Image image = Bitmap.FromFile(filename))
            {
                using (Bitmap bitmap = new Bitmap(image))
                {
                    fp.AsBitmap = bitmap;
                }
            }

            //创建人对象
            Person person = new Person();
            person.Fingerprints.Add(fp);    //加入指纹

            //提取指纹摸版
            afis.Extract(person);

            return fp;
        }
    }
}
